/*************************************
 * Joe Helgeson
 * CS362 Assignment 3
 * Unit tests for various 
 * non-card-specific functions
 *
 * unittest1.c test for shuffle()
 * 
 * (tests that at least 1 card in
 * the deck has been shuffled)
 *************************************/

#include "dominion.h"
#include "dominion_helpers.h"
#include "rngs.h"
#include <stdio.h>
#include <math.h>
#include <stdlib.h>
#include <assert.h>

//enable debugging messages
//#ifdef DEBUG
//#undef DEBUG
//#endif
//#define DEBUG 1

void testIt(struct gameState* tState, int numCards);

////////////////////////////////////////
int main(int argc, char const** argv) {
	struct gameState* tState = malloc(sizeof(struct gameState));

	//test up to 500 cards (=MAX_HAND)
	int numCards;
	for(numCards = 0; numCards<MAX_HAND; numCards++) {

		printf("For a deck of %d cards: ", numCards);
		testIt(tState, numCards);
	}
	
	free(tState);
	return 0;
}

/////////////////////////////////////////////////////
void testIt(struct gameState* tState, int numCards) {

	//init deck count
	tState->deckCount[0] = 0;

	//make a deck
	int i;
	for (i=0; i<numCards; i++) {
		//generate each card (using just 1 player) from the 27 types available,
		tState->deck[0][i] = rand() % 27;
		//and increase deck size accordingly
		tState->deckCount[0]++;
	}

	//save a backup of the ("original") deck to compare against after shuffling
	struct gameState* tStateOrig = malloc(sizeof(struct gameState));
	for (i=0; i<numCards; i++) {
		//copy each card over to new deck
		tStateOrig->deck[0][i] = tState->deck[0][i];
		tStateOrig->deckCount[0]++;
	}

	//run shuffle
	int res = shuffle(0, tState);
	
	//some corner cases
	//check if deck is empty (should return -1)
	if ((res != -1) && (tState->deckCount[0] == 0)) {
		printf("Test Failed for empty deck (did not return -1).\n");
		free(tStateOrig);
		return;
	}
	if  ((res == -1) && (tState->deckCount[0] == 0)) {
		printf("Test Passed for empty deck.\n");
		free(tStateOrig);
		return;
	}

	//check that if deck not empty, shuffle() should not return -1
	if ((res == -1) && (tState->deckCount[0] != 0)) {
		printf("Test Failed for non-empty deck (returned -1).\n");
		free(tStateOrig);
		return;
	}

	//check if card in deck (card value should not change)
	if (tState->deckCount[0] == 1) {
		if (tState->deck[0][0] == tStateOrig->deck[0][0]) {
			printf("Test Passed for one-card-in-deck scenario.\n");
		}
		else {
			printf("Test Failed for one-card-in-deck scenario.\n");
		}
	free(tStateOrig);
	return;
	}

	//anything else
	//verify shuffled deck is different from original by at least 1 card
	int same = 1;
	for (i=0; i<numCards; i++) {
		if (tState->deck[0][i] != tStateOrig->deck[0][i]) { //some different card order exists
			same = 0;
			break;
		}
	}
	if (same == 1) {
		printf("Test Failed, cards are not shuffled.\n");
	}
	else {
		printf("Test Passed, cards are shuffled.\n");
	}
	free(tStateOrig);
	return;
}

